using System;
using System.Data.Common;
using System.Data;
using System.Collections.Generic;

namespace FROG
{
    public class OpenConnection : IDisposable
    {
        public OpenConnection(Database db)
        {
            _database = db;
            _connection = _database.CreateDbConnection();
            _autoCommit = _database.AutoCommit;
            App.OpenConnections.Add(this);
        }

        ~OpenConnection()
        {
            Dispose(false);

        }

        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        public void Dispose(bool disposing)
        {
            App.OpenConnections.Remove(this);
            this.Close();
        }

        private Database _database;
        public Database Database
        {
            get { return _database; }
        }

        private DbConnection _connection;
        public DbConnection Connection
        {
            get { return _connection; }
        }

        private bool _autoCommit;
        public bool AutoCommit
        {
            get { return _autoCommit; }
        }

        private DbTransaction _transaction;

        public DbCommand CreateCommand()
        {
            DbCommand cmd = _connection.CreateCommand();
            cmd.Transaction = _transaction;
            return cmd;
        }

        public void Open()
        {
            _connection.Open();
            _autoCommit = _database.AutoCommit;
            if (!_autoCommit)
            {
                _transaction = _connection.BeginTransaction();
            }
            OnConnectionOpened();
        }

        public void Close()
        {
            if (_connection != null && (_connection.State & ConnectionState.Open) == ConnectionState.Open)
            {
                try
                {
                    _connection.Close();
                }
                catch
                {
                }
                OnConnectionClosed();
            }
        }

        public void Commit()
        {
            if (!_autoCommit)
            {
                _transaction.Commit();
                _transaction = _connection.BeginTransaction();
            }
        }

        public void Rollback()
        {
            if (!_autoCommit)
            {
                _transaction.Rollback();
                _transaction = _connection.BeginTransaction();
            }
        }

        public event EventHandler ConnectionOpened;
        public event EventHandler ConnectionClosed;

        protected void OnConnectionOpened()
        {
            if (ConnectionOpened != null)
                ConnectionOpened(this, EventArgs.Empty);
        }

        protected void OnConnectionClosed()
        {
            if (ConnectionClosed != null)
                ConnectionClosed(this, EventArgs.Empty);
        }

        private List<string> blobTypes
            = new List<string>(
                new string[] {
                    "BLOB",
                    "BINARY",
                    "VARBINARY",
                    "LONG VARBINARY",
                    "RAW",
                    "LONG RAW"
                });

        public bool IsBlobType(string dataTypeName)
        {
            if (blobTypes.Contains(dataTypeName))
                return true;
            else
                return false;
        }
    }
}
